<template>
  <div class="page_root" :key="queryUpdateFlag" data-page-name="月度目标管理(新版)" data-page-identification="c_i0ngsrcxvq">
    <a-spin :spinning="pageLoading.loading" :tip="pageLoading.tip">
      <!-- begin vid_p2x31ulxw6 自定义模板_gufjjaz2ct -->
      <a-modal
        centered
        :visible="state.completeVisible"
        width="100%"
        @cancel="state.completeVisible = false"
        wrapClassName="modal-title"
        :body-style="{
                    maxHeight: '800px',
                    overflowY: 'auto',
                    paddingBottom: '16px'
                }"
        destroy-on-close
        @ok="submitComplete"
        :ok-button-props="{ loading: state.okLoading }"
      >
        <template #title>{{ state.type === '完成系数' ? '非目标项目完成系数' : '项目配置' }}</template>
        <div class="modal-top-complete" v-if="state.type === '完成系数'">
          <a-col :span="12" style="height: 32px; margin-bottom: 8px">
            <a-form-item label="月份">
              <a-date-picker v-model:value="state.filter.month" picker="month" value-format="YYYY-MM" style="width: 100%" :allowClear="false" @change="getComplete" />
            </a-form-item>
          </a-col>
        </div>
        <div class="modal-top-setting" v-else>该弹窗内选“<span style="font-weight: 800">是</span>”的项目支持创建月度目标和设置完成系数</div>
        <a-spin :spinning="treeLoading" tip="加载中">
          <div class="no-target">
            <a-form :model="state.treeData" ref="form">
              <!-- 使用 v-model:activeKey 绑定 activeKeys，用于控制面板的展开折叠 -->
              <a-collapse v-model:activeKey="activeKeys">
                <a-collapse-panel :key="outItem.projectId" v-for="(outItem, outIndex) in state.treeData" :header="outItem.projectName">
                  <div class="border-line">
                    <!-- 渲染子节点 -->
                    <div v-for="(childrenItem, innerIndex) in outItem.children" :key="childrenItem.id" class="inner-item">
                      <a-row v-if="!childrenItem.children || childrenItem.children.length === 0" style="margin-bottom: 12px; height: 32px">
                        <a-col :span="12" style="height: 32px">
                          <div class="inner-title">
                            <span class="child-icon">
                              <FileOutlined />
                            </span>
                            {{ childrenItem.projectName }}
                          </div>
                        </a-col>
                        <a-col :span="12" v-if="!childrenItem.disabled && state.type === '完成系数'">
                          <a-form-item label="完成系数">
                            <a-input-number style="width: 100%" v-model:value="childrenItem.finishCoefficient" :min="0" :step="0.01" :precision="2" placeholder="请输入(支持两位小数)" />
                          </a-form-item>
                        </a-col>
                        <a-col :span="4" v-if="!childrenItem.disabled && state.type === '是否展示'">
                          <a-form-item label="">
                            <a-radio-group v-model:value="childrenItem.flag">
                              <a-radio value="是">是</a-radio>
                              <a-radio value="否">否</a-radio>
                            </a-radio-group>
                          </a-form-item>
                        </a-col>
                        <a-col :span="8" v-if="!childrenItem.disabled && state.type === '是否展示'">
                          <a-form-item label="目标创建人">
                            <a-select
                              :options="peopleList"
                              :allowClear="true"
                              mode="multiple"
                              :placeholder="selectHolder"
                              :dropdownMatchSelectWidth="true"
                              :showSearch="true"
                              :filterOption="
                                                                (input, option) => {
                                                                    return (
                                                                        option.label
                                                                            .toLowerCase()
                                                                            .indexOf(input.toLowerCase()) >= 0
                                                                    )
                                                                }
                                                            "
                              :showArrow="true"
                              v-model:value="childrenItem.createUserIds"
                            />
                          </a-form-item>
                        </a-col>
                      </a-row>

                      <!-- 子节点折叠 -->
                      <a-collapse v-if="childrenItem.children && childrenItem.children.length > 0" v-model:activeKey="activeKeys">
                        <a-collapse-panel :header="childrenItem.projectName" :key="childrenItem.projectId">
                          <div class="border-line">
                            <!-- 子节点递归渲染 -->
                            <div v-for="(subChildrenItem, subIndex) in childrenItem.children" :key="subChildrenItem.id" class="child-item">
                              <a-row
                                v-if="
                                                                    !subChildrenItem.children ||
                                                                    subChildrenItem.children.length === 0
                                                                "
                                style="height: 32px; margin-bottom: 12px"
                              >
                                <a-col :span="12" style="height: 32px">
                                  <div class="inner-title" style="margin-left: 12px">
                                    <span class="child-icon">
                                      <FileOutlined />
                                    </span>
                                    {{ subChildrenItem.projectName }}
                                  </div>
                                </a-col>
                                <a-col
                                  :span="12"
                                  v-if="
                                                                        !subChildrenItem.disabled &&
                                                                        state.type === '完成系数'
                                                                    "
                                  style="height: 32px"
                                >
                                  <a-form-item label="完成系数 ">
                                    <a-input-number
                                      style="width: 100%"
                                      v-model:value="
                                                                                subChildrenItem.finishCoefficient
                                                                            "
                                      :min="0"
                                      :step="0.01"
                                      :precision="2"
                                      placeholder="请输入(支持两位小数)"
                                    />
                                  </a-form-item>
                                </a-col>
                                <a-col
                                  :span="4"
                                  v-if="
                                                                        !subChildrenItem.disabled &&
                                                                        state.type === '是否展示'
                                                                    "
                                >
                                  <a-form-item label="">
                                    <a-radio-group v-model:value="subChildrenItem.flag">
                                      <a-radio value="是">是</a-radio>
                                      <a-radio value="否">否</a-radio>
                                    </a-radio-group>
                                  </a-form-item>
                                </a-col>
                                <a-col
                                  :span="8"
                                  v-if="
                                                                        !subChildrenItem.disabled &&
                                                                        state.type === '是否展示'
                                                                    "
                                >
                                  <a-form-item label="目标创建人">
                                    <a-select
                                      :options="peopleList"
                                      :allowClear="true"
                                      mode="multiple"
                                      :placeholder="selectHolder"
                                      :dropdownMatchSelectWidth="true"
                                      :showSearch="true"
                                      :filterOption="
                                                                                (input, option) => {
                                                                                    return (
                                                                                        option.label
                                                                                            .toLowerCase()
                                                                                            .indexOf(
                                                                                                input.toLowerCase()
                                                                                            ) >= 0
                                                                                    )
                                                                                }
                                                                            "
                                      :showArrow="true"
                                      v-model:value="
                                                                                subChildrenItem.createUserIds
                                                                            "
                                    />
                                  </a-form-item>
                                </a-col>
                              </a-row>

                              <!-- 递归渲染子节点的子节点 -->
                              <a-collapse
                                v-if="
                                                                    subChildrenItem.children &&
                                                                    subChildrenItem.children.length > 0
                                                                "
                                v-model:activeKey="activeKeys"
                              >
                                <a-collapse-panel :header="subChildrenItem.projectName" :key="subChildrenItem.projectId">
                                  <div class="border-line">
                                    <div
                                      v-for="(
                                                                                subSubChildrenItem, subSubIndex
                                                                            ) in subChildrenItem.children"
                                      :key="subSubChildrenItem.id"
                                    >
                                      <a-row
                                        v-if="
                                                                                    !subSubChildrenItem.children ||
                                                                                    subSubChildrenItem.children
                                                                                        .length === 0
                                                                                "
                                        style="
                                                                                    height: 32px;
                                                                                    margin-bottom: 12px;
                                                                                "
                                      >
                                        <a-col :span="12" style="height: 32px">
                                          <div class="inner-title" style="margin-left: 12px">
                                            <span class="child-icon">
                                              <FileOutlined />
                                            </span>
                                            {{
                                              subSubChildrenItem.projectName
                                            }}
                                          </div>
                                        </a-col>
                                        <a-col
                                          :span="12"
                                          v-if="
                                                                                        !subSubChildrenItem.disabled &&
                                                                                        state.type === '完成系数'
                                                                                    "
                                          style="height: 32px"
                                        >
                                          <a-form-item label="完成系数">
                                            <a-input-number
                                              style="width: 100%"
                                              v-model:value="
                                                                                                subSubChildrenItem.finishCoefficient
                                                                                            "
                                              :min="0"
                                              :step="0.01"
                                              :precision="2"
                                              placeholder="请输入(支持两位小数)"
                                            />
                                          </a-form-item>
                                        </a-col>
                                        <a-col
                                          :span="4"
                                          v-if="
                                                                                        !subSubChildrenItem.disabled &&
                                                                                        state.type === '是否展示'
                                                                                    "
                                        >
                                          <a-form-item label="">
                                            <a-radio-group
                                              v-model:value="
                                                                                                subSubChildrenItem.flag
                                                                                            "
                                            >
                                              <a-radio value="是">是</a-radio>
                                              <a-radio value="否">否</a-radio>
                                            </a-radio-group>
                                          </a-form-item>
                                        </a-col>
                                        <a-col
                                          :span="8"
                                          v-if="
                                                                                        !subSubChildrenItem.disabled &&
                                                                                        state.type === '是否展示'
                                                                                    "
                                        >
                                          <a-form-item label="目标创建人">
                                            <a-select
                                              :options="peopleList"
                                              :allowClear="true"
                                              :placeholder="selectHolder"
                                              mode="multiple"
                                              :dropdownMatchSelectWidth="
                                                                                                true
                                                                                            "
                                              :showSearch="true"
                                              :filterOption="
                                                                                                (input, option) => {
                                                                                                    return (
                                                                                                        option.label
                                                                                                            .toLowerCase()
                                                                                                            .indexOf(
                                                                                                                input.toLowerCase()
                                                                                                            ) >= 0
                                                                                                    )
                                                                                                }
                                                                                            "
                                              :showArrow="true"
                                              v-model:value="
                                                                                                subSubChildrenItem.createUserIds
                                                                                            "
                                            />
                                          </a-form-item>
                                        </a-col>
                                      </a-row>
                                    </div>
                                  </div>
                                </a-collapse-panel>
                              </a-collapse>
                            </div>
                          </div>
                        </a-collapse-panel>
                      </a-collapse>
                    </div>
                  </div>
                </a-collapse-panel>
              </a-collapse>
            </a-form>
          </div>
        </a-spin>
      </a-modal>
      <!--            甘特图-->
      <a-modal
        :visible="targetState.ganteVisible"
        title="目标甘特图"
        :footer="null"
        centered
        @cancel="cancelGante"
        width="100%"
        :body-style="{
                    maxHeight: '800px',
                    overflowY: 'auto'
                }"
      >
        <Gante v-if="targetState.ganteVisible" :time="gantMonth" :projectName="gantProjectName" />
      </a-modal>
      <!--            甘特图-->
      <!--            查看问题-->
      <a-modal
        :visible="showMsgState.visible"
        title="用户故事描述"
        :footer="null"
        centered
        @cancel="cancelShowMsg"
        width="1000px"
        :body-style="{
                    maxHeight: '800px',
                    overflowY: 'auto'
                }"
      >
        <div class="item-content" v-html="getHtmlContent(showMsgState.msg)"> </div>
      </a-modal>
      <!--            查看问题-->
      <!--            新建/编辑用户故事-->
      <a-modal
        :visible="milepostState.addOrEditVisible"
        :title="milepostState.addOrEditTitle"
        centered
        :mask-closable="false"
        destroy-on-close
        :body-style="{
                    maxHeight: '800px',
                    overflowY: 'auto'
                }"
        width="1000px"
        @cancel="cancelStory"
      >
        <template #footer>
          <a-button type="primary" @click="cancleMbTask"> 取消</a-button>
          <a-button
            type="primary"
            v-if="
                            milepostState.current == 1 &&
                            milepostState.modalForm.templateTaskId?.length > 0 &&
                            !currentData.id
                        "
            @click="getTask"
            :loading="milepostState.nextLoading"
          >
            下一步</a-button
          >
          <a-button type="primary" v-if="milepostState.current == 2" @click="milepostState.current = 1"> 上一步</a-button>
          <a-button
            type="primary"
            @click="confirmMbTask"
            v-if="
                            milepostState.current == 2 ||
                            (milepostState.modalForm.templateTaskId?.length == 0 && milepostState.current == 1)
                        "
            :loading="milepostState.okLoading"
          >
            确定</a-button
          >
        </template>
        <div class="form-model">
          <a-form :model="milepostState.modalForm" ref="formRef" :rules="rules">
            <a-row v-if="milepostState.current == 1">
              <a-col :span="12">
                <a-form-item label="月份">
                  <a-date-picker
                    v-model:value="milepostState.modalForm.monthlyGoalTargetMonth"
                    value-format="YYYY-MM"
                    picker="month"
                    style="width: 100%"
                    @change="milepostState.modalForm.projectMonthlyGoalManagementId = undefined"
                  />
                </a-form-item>
              </a-col>
              <a-col :span="12">
                <a-form-item label="月度子目标">
                  <a-select
                    :options="milepostState.targetList"
                    v-model:value="milepostState.modalForm.projectMonthlyGoalManagementId"
                    show-search
                    :placeholder="selectHolder"
                    :filterOption="
                                            (input, option) => {
                                                return option.label.toLowerCase().indexOf(input.toLowerCase()) >= 0
                                            }
                                        "
                    allow-clear
                    @focus="getTarget"
                  />
                </a-form-item>
              </a-col>
              <a-col :span="24">
                <a-form-item label="用户故事名称" name="storyName">
                  <a-input v-model:value="milepostState.modalForm.storyName" :placeholder="inputHolder" />
                </a-form-item>
              </a-col>
              <a-col :span="12">
                <a-form-item label="计划起止时间">
                  <a-range-picker style="width: 100%" v-model:value="milepostState.modalForm.timeRangeList" valueFormat="YYYY-MM-DD" />
                </a-form-item>
              </a-col>
              <a-col :span="12">
                <a-form-item label="优先级" name="priority" :rules="[{ required: true, msssage: '请选择优先级', trigger: 'blur' }]">
                  <a-select
                    :options="[
                                            {
                                                label: 'P0',
                                                value: 'P0'
                                            },
                                            {
                                                label: 'P1',
                                                value: 'P1'
                                            },
                                            {
                                                label: 'P2',
                                                value: 'P2'
                                            },
                                            {
                                                label: 'P3',
                                                value: 'P3'
                                            }
                                        ]"
                    :placeholder="selectHolder"
                    v-model:value="milepostState.modalForm.priority"
                  />
                </a-form-item>
              </a-col>
              <a-col :span="24">
                <a-form-item label="描述" name="labels">
                  <QuillEditor v-model:content="milepostState.modalForm.description" ref="quillEditor" :options="editorOption" class="quill-editor" />
                </a-form-item>
              </a-col>
              <a-col :span="24">
                <a-form-item label="标签" name="labels">
                  <a-input v-model:value="milepostState.modalForm.labels" show-count :placeholder="inputHolder" />
                </a-form-item>
              </a-col>
              <a-col :span="24" v-if="!currentData.id">
                <a-form-item
                  label="功能简称"
                  name="functionAbbreviation"
                  :rules="[
                                        {
                                            required: milepostState.modalForm.templateTaskId.length > 0 ? true : false,
                                            message: '请输入功能简称',
                                            trigger: 'blur'
                                        }
                                    ]"
                >
                  <a-input :placeholder="inputHolder" v-model:value="milepostState.modalForm.functionAbbreviation" maxlength="10" show-count />
                </a-form-item>
              </a-col>
              <a-col :span="24" v-if="!currentData.id">
                <a-form-item label="SOP任务">
                  <a-tree-select
                    v-model:value="milepostState.modalForm.templateTaskId"
                    show-search
                    multiple
                    treeCheckable
                    style="width: 100%"
                    placeholder="请选择"
                    allow-clear
                    treeDefaultExpandAll
                    :tree-data="milepostState.treeData"
                    :fieldNames="{
                                            children: 'children',
                                            label: 'taskName',
                                            value: 'taskId',
                                            key: 'taskId'
                                        }"
                    :filterTreeNode="
                                            (inputValue, treeNode) => {
                                                return (
                                                    treeNode.taskName.toLowerCase().indexOf(inputValue.toLowerCase()) >=
                                                    0
                                                )
                                            }
                                        "
                    :max-tag-count="7"
                    @focus="getTreeData"
                  />
                </a-form-item>
              </a-col>
              <a-col :span="24">
                <a-form-item label="备注">
                  <a-textarea v-model:value="milepostState.modalForm.remarks" :placeholder="inputHolder" />
                </a-form-item>
              </a-col>
            </a-row>
            <div v-else>
              <div v-for="(item, index) in milepostState.modalForm.taskList" :key="index" class="form-item">
                <div class="form-content">
                  <a-row class="one-line">
                    <a-col :span="24">
                      <a-form-item
                        label="任务名称"
                        :name="['taskList', index, 'taskName']"
                        :rules="[
                                                    {
                                                        required: true,
                                                        message: '请输入任务名称!'
                                                    },
                                                    {
                                                        validator: () => {
                                                            if (milepostState.modalForm.taskList[index].taskName) {
                                                                if (
                                                                    milepostState.modalForm.taskList[
                                                                        index
                                                                    ].taskName.trim()
                                                                ) {
                                                                    return PromiseProxy.resolve()
                                                                } else {
                                                                    return PromiseProxy.reject('请输入任务名称!')
                                                                }
                                                            } else {
                                                                return PromiseProxy.resolve()
                                                            }
                                                        }
                                                    }
                                                ]"
                      >
                        <a-input disabled :placeholder="inputHolder" v-model:value="milepostState.modalForm.taskList[index].taskName" />
                      </a-form-item>
                    </a-col>
                  </a-row>

                  <a-row>
                    <a-col :span="12">
                      <a-form-item
                        label="预计投入工时"
                        :name="['taskList', index, 'workingHours']"
                        :rules="[
                                                    { required: true, message: '请输入预计投入工时!', trigger: 'blur' },
                                                    {
                                                        pattern: /^(0\.5|[1-9](\d*)?(\.5)?(\.0)?)$/,
                                                        message: '请输入大于0的数字(支持0.5的倍数)',
                                                        trigger: 'blur'
                                                    }
                                                ]"
                      >
                        <a-input placeholder="请输入工时(支持0.5的数字)" v-model:value="milepostState.modalForm.taskList[index].workingHours" :min="0" type="number" suffix="小时" />
                      </a-form-item>
                    </a-col>
                    <a-col :span="12">
                      <a-form-item label="任务起止时间" :name="['taskList', index, 'allTime']" :rules="{ required: true, message: '请选择任务起止时间!' }">
                        <a-range-picker style="width: 100%" v-model:value="milepostState.modalForm.taskList[index].allTime" valueFormat="YYYY-MM-DD" />
                      </a-form-item>
                    </a-col>
                  </a-row>
                  <a-row>
                    <a-col :span="12">
                      <a-form-item label="任务负责人" :name="['taskList', index, 'taskOwner']" :rules="{ required: true, message: '请选择任务负责人!' }">
                        <a-select
                          :placeholder="selectHolder"
                          v-model:value="milepostState.modalForm.taskList[index].taskOwner"
                          showSearch
                          :options="peopleList"
                          :field-names="{ label: 'label', value: 'value' }"
                          :filter-option="
                                                        (input, option) => {
                                                            return (
                                                                option.label
                                                                    .toLowerCase()
                                                                    .indexOf(input.toLowerCase()) >= 0
                                                            )
                                                        }
                                                    "
                        />
                      </a-form-item>
                    </a-col>
                    <a-col :span="12">
                      <a-form-item label="审核员" :name="['taskList', index, 'assessorName']" :rules="{ required: true, message: '请选择审核员!' }">
                        <a-select
                          :placeholder="selectHolder"
                          v-model:value="milepostState.modalForm.taskList[index].assessorName"
                          showSearch
                          :options="peopleList"
                          :field-names="{ label: 'label', value: 'value' }"
                          :filter-option="
                                                        (input, option) => {
                                                            return (
                                                                option.label
                                                                    .toLowerCase()
                                                                    .indexOf(input.toLowerCase()) >= 0
                                                            )
                                                        }
                                                    "
                        />
                      </a-form-item>
                    </a-col>
                  </a-row>
                  <a-row class="one-line">
                    <a-col :span="24">
                      <a-form-item label="任务执行人" :name="['taskList', index, 'taskParticipantList']" :rules="{ required: true, message: '请选择任务参与人!' }">
                        <a-select
                          :placeholder="selectHolder"
                          v-model:value="
                                                        milepostState.modalForm.taskList[index].taskParticipantList
                                                    "
                          showSearch
                          mode="multiple"
                          :options="peopleList"
                          :field-names="{ label: 'label', value: 'value' }"
                          :filter-option="
                                                        (input, option) => {
                                                            return (
                                                                option.label
                                                                    .toLowerCase()
                                                                    .indexOf(input.toLowerCase()) >= 0
                                                            )
                                                        }
                                                    "
                        />
                      </a-form-item>
                    </a-col>
                  </a-row>
                  <a-row>
                    <a-col v-if="taskPeopleList.length > 0">
                      <div style="width: 700px; margin-left: 115px; margin-bottom: 28px">
                        <a href="javascript:;" v-for="(item, num) in taskPeopleList" @click="handlerAddPtMbPeople(item.value, index)"
                          ><span style="margin: 0 5px">{{ item.value }}</span></a
                        >
                      </div>
                    </a-col>
                  </a-row>
                  <a-row class="one-line">
                    <a-col :span="24">
                      <a-form-item label="备注">
                        <a-textarea v-model:value="milepostState.modalForm.taskList[index].remark" :placeholder="inputHolder" />
                      </a-form-item>
                    </a-col>
                  </a-row>
                </div>
              </div>
            </div>
          </a-form>
        </div>
      </a-modal>
      <!--            新建/编辑用户故事-->
      <!--        新建/编辑月度目标    -->
      <a-modal
        :visible="targetState.addOrEditVisible"
        :title="targetState.addOrEditTitle"
        centered
        width="800px"
        :body-style="{
                    maxHeight: '800px',
                    overflowY: 'auto'
                }"
        destroy-on-close
        @ok="submitTarget"
        @cancel="cancelTarget"
        :ok-button-props="{ loading: targetState.targetLoadog }"
      >
        <div class="modal-form">
          <a-form :model="targetState.modalForm" ref="targetFormRef">
            <a-row>
              <a-col :span="11">
                <a-form-item label="目标月份" :rules="[{ required: true, message: '请选择目标月份', trigger: 'blur' }]" name="targetMonth">
                  <a-date-picker style="width: 100%" picker="month" v-model:value="targetState.modalForm.targetMonth" value-format="YYYY-MM" />
                </a-form-item>
              </a-col>
              <a-col :span="11" />
              <a-col :span="11">
                <a-form-item label="项目类型" :rules="[{ required: true, message: '请选择项目类型', trigger: 'blur' }]" name="projectType">
                  <a-select
                    :options="[
                                            {
                                                label: '产品研发',
                                                value: '产品研发'
                                            },
                                            {
                                                label: '交付',
                                                value: '交付'
                                            },
                                            {
                                                label: '市场',
                                                value: '市场'
                                            }
                                        ]"
                    :placeholder="selectHolder"
                    v-model:value="targetState.modalForm.projectType"
                    @change="targetState.modalForm.associationProjectId = undefined"
                  />
                </a-form-item>
              </a-col>
              <a-col :span="11">
                <a-form-item label="项目名称" :rules="[{ required: true, message: '请选择项目名称', trigger: 'blur' }]" name="projectName">
                  <a-select
                    :options="targetState.projectList"
                    v-model:value="targetState.modalForm.projectName"
                    :filterOption="
                                            (input, option) => {
                                                return option.label.toLowerCase().indexOf(input.toLowerCase()) >= 0
                                            }
                                        "
                    :placeholder="selectHolder"
                    @focus="getProjectListAccordingType"
                  />
                </a-form-item>
              </a-col>
              <a-divider style="margin-bottom: 16px; margin-top: 0" />
              <a-col :span="22">
                <a-form-item label="项目总目标" :rules="[{ required: true, message: '请输入项目总目标', trigger: 'blur' }]" name="totalMonthlyGoal">
                  <a-textarea v-model:value="targetState.modalForm.totalMonthlyGoal" :placeholder="inputHolder" />
                </a-form-item>
              </a-col>
              <a-col :span="11">
                <a-form-item label="团队负责人" :rules="[{ required: true, message: '请选择团队负责人', trigger: 'blur' }]" name="teamLeader">
                  <a-select
                    :placeholder="selectHolder"
                    show-search
                    :options="targetState.allUser"
                    v-model:value="targetState.modalForm.teamLeader"
                    :filterOption="
                                            (input, option) => {
                                                return option.label.toLowerCase().indexOf(input.toLowerCase()) >= 0
                                            }
                                        "
                  />
                </a-form-item>
              </a-col>
              <a-col :span="11">
                <a-form-item label="负责人" :rules="[{ required: true, message: '请选择负责人', trigger: 'blur' }]" name="leaderList">
                  <a-select
                    show-search
                    mode="multiple"
                    :placeholder="selectHolder"
                    :options="targetState.allUser"
                    v-model:value="targetState.modalForm.leaderList"
                    :filterOption="
                                            (input, option) => {
                                                return option.label.toLowerCase().indexOf(input.toLowerCase()) >= 0
                                            }
                                        "
                  />
                </a-form-item>
              </a-col>
              <a-col :span="24">
                <div v-for="(item, index) in targetState.modalForm.monthlyGoalObjectList" :key="index">
                  <a-row>
                    <a-col :span="22">
                      <a-form-item label="子目标" :rules="[{ required: true, message: '请输入子目标', trigger: 'blur' }]" :name="['monthlyGoalObjectList', index, 'monthlyGoal']">
                        <a-textarea
                          v-model:value="
                                                        targetState.modalForm.monthlyGoalObjectList[index].monthlyGoal
                                                    "
                          :placeholder="inputHolder"
                        />
                      </a-form-item>
                    </a-col>
                    <a-col :span="2">
                      <a-button @click="handleDeleteTargetItem(index)" type="link">删除</a-button>
                    </a-col>
                    <a-col :span="22">
                      <a-form-item label="验收标准">
                        <a-textarea
                          v-model:value="
                                                        targetState.modalForm.monthlyGoalObjectList[index]
                                                            .acceptanceCriteria
                                                    "
                          :placeholder="inputHolder"
                        />
                      </a-form-item>
                    </a-col>
                  </a-row>
                </div>
              </a-col>
              <a-col :span="22">
                <a-button @click="handleAddTargetItem" type="primary" ghost
                  ><template #icon><plus-outlined /></template> 新增</a-button
                >
              </a-col>
            </a-row>
          </a-form>
        </div>
      </a-modal>
      <!--        新建/编辑月度目标    -->
      <div class="body">
        <div class="top-search">
          <a-row>
            <a-col :span="21">
              <a-row>
                <a-col :span="6">
                  <a-form-item :label-col="{ span: 6 }" :wrapper-col="{ span: 18 }" label="月份筛选">
                    <a-range-picker v-model:value="state.searchForm.targetMonthList" picker="month" value-format="YYYY-MM" />
                  </a-form-item>
                </a-col>
                <a-col :span="6">
                  <a-form-item :label-col="{ span: 6 }" :wrapper-col="{ span: 18 }" label="项目类型">
                    <a-select
                      mode="multiple"
                      :options="[
                                                {
                                                    label: '交付',
                                                    value: '交付'
                                                },
                                                {
                                                    label: '产品研发',
                                                    value: '产品研发'
                                                },
                                                {
                                                    label: '市场',
                                                    value: '市场'
                                                }
                                            ]"
                      :placeholder="selectHolder"
                      :filterOption="
                                                (input, option) => {
                                                    return option.label.toLowerCase().indexOf(input.toLowerCase()) >= 0
                                                }
                                            "
                      show-search
                      v-model:value="state.searchForm.projectTypeList"
                    />
                  </a-form-item>
                </a-col>
                <a-col :span="6">
                  <a-form-item :label-col="{ span: 6 }" :wrapper-col="{ span: 18 }" label="项目名称">
                    <a-select
                      :mode="'multiple'"
                      :options="state.projectList"
                      v-model:value="state.searchForm.projectNameList"
                      @focus="getProjectList"
                      show-search
                      :placeholder="selectHolder"
                      :filterOption="
                                                (input, option) => {
                                                    return option.label.toLowerCase().indexOf(input.toLowerCase()) >= 0
                                                }
                                            "
                    />
                  </a-form-item>
                </a-col>
                <a-col :span="6">
                  <a-form-item :label-col="{ span: 6 }" :wrapper-col="{ span: 18 }" label="负责人">
                    <a-select
                      :mode="'multiple'"
                      :options="state.allUser"
                      v-model:value="state.searchForm.leaderList"
                      @focus="getAllUser"
                      show-search
                      :placeholder="selectHolder"
                      :filterOption="
                                                (input, option) => {
                                                    return option.label.toLowerCase().indexOf(input.toLowerCase()) >= 0
                                                }
                                            "
                    />
                  </a-form-item>
                </a-col>
              </a-row>
            </a-col>
            <a-col :span="3" style="display: flex; flex-direction: row; justify-content: flex-end; align-items: start">
              <a-space>
                <a-button @click="getData" type="primary">查询</a-button>
                <a-button @click="resetData" type="primary" ghost>重置</a-button>
              </a-space>
            </a-col>
          </a-row>
        </div>
        <div class="top-title">
          <div class="title-msg">项目月度目标管理</div>
          <div class="title-right">
            <a-space :size="16">
              <a-button @click="handleExpendAll" type="primary" ghost>{{
                  allExpanded ? '全部收起' : '全部展开'
              }}</a-button>
              <a-button type="primary" ghost @click="handleExport"
                ><template #icon><upload-outlined /></template> 导出</a-button
              >
              <a-button type="primary" @click="handleAddTarget">新建</a-button>
              <a-button type="primary" ghost :loading="targetState.generateLoading" @click="handleGenerate"
                ><template #icon><user-add-outlined /></template>生成员工绩效</a-button
              >
              <a-button type="primary" ghost @click="showSettingModal"
                ><template #icon><setting-outlined /></template>项目配置</a-button
              >
              <a-button type="primary" ghost @click="showCompleteModal"
                ><template #icon><reconciliation-outlined /></template>批量修改项目完成系数</a-button
              >
            </a-space>
          </div>
        </div>

        <div class="content">
          <a-spin :spinning="targetState.loading" tip="加载中">
            <div class="no-data-image" v-if="targetState.dataSource.length == 0">
              <div class="no-date-tip"> 暂无数据 </div>
            </div>
            <div v-for="goal in targetState.dataSource" :key="goal.id" class="goal-card">
              <div class="goal-title-bar">
                <div class="goal-info">
                  <div class="goal-month ft16">{{ goal.targetMonth }}</div>
                  <div class="goal-product-jf" v-if="goal.projectType === '交付'">{{
                      goal.projectType
                  }}</div>
                  <div class="goal-product-cp" v-if="goal.projectType === '产品研发'">{{
                      goal.projectType
                  }}</div>
                  <div class="goal-product-sc" v-if="goal.projectType === '市场'">{{
                      goal.projectType
                  }}</div>
                  <div class="goal-name" :title="goal.projectName">{{ goal.projectName }}</div>
                </div>
                <div class="goal-ops">
                  <div class="approve-img"></div>
                  <div>
                    <span class="ft-label">审批状态：</span>
                    <span class="ft14">{{ goal.approvalStatus }}</span>
                  </div>
                  <div class="time-img"></div>
                  <div>
                    <span class="ft-label">提交时间：</span>
                    <span class="ft14">{{ goal.modifiedTime }}</span>
                  </div>
                  <!--                                    <a-button type="link" size="small" class="btn-no-margin" @click="showHidden(goal)"-->
                  <!--                                        >取消展示</a-button-->
                  <!--                                    >-->
                  <!--                                    <a-divider type="vertical" style="background-color: #3875ff; margin: 0" />-->
                  <a-button type="link" size="small" class="btn-no-margin" @click="handleAssociation(goal)">关联</a-button>
                  <a-divider type="vertical" style="background-color: #3875ff; margin: 0" />
                  <a-button type="link" size="small" class="btn-no-margin" @click="showGante(goal)">甘特图</a-button>
                  <a-divider type="vertical" style="background-color: #3875ff; margin: 0" />
                  <a-button type="link" size="small" class="btn-no-margin" @click="handleEditGoal(goal)">编辑</a-button>
                  <a-divider type="vertical" style="background-color: #3875ff; margin: 0" />
                  <a-popconfirm placement="left" title="确定删除吗?" ok-text="确定" cancel-text="取消" @confirm="confirmDeleteGoal(goal)" @cancel="cancel">
                    <a-button type="link" size="small" class="btn-no-margin">删除</a-button>
                  </a-popconfirm>
                </div>
              </div>
              <div class="first-line">
                <div class="line-item">
                  <div class="xs-img"></div>
                  <span class="ft-label">完成系数：</span>
                  <span class="ft14">{{ goal.finishCoefficient }}</span>
                </div>
                <div class="line-item">
                  <div class="trd-img"></div>
                  <span class="ft-label">投入度总数：</span>
                  <span class="ft14">{{ goal.investment }}</span>
                </div>
                <div class="line-item">
                  <div class="tl-img"></div>
                  <span class="ft-label">团队负责人：</span>
                  <span class="ft14">{{ goal.teamLeader }}</span>
                </div>
                <div class="line-item">
                  <div class="fzr-img"></div>
                  <span class="ft-label">负责人：</span>
                  <span class="ft14">{{ goal.leader }}</span>
                </div>
              </div>
              <div class="second-line">
                <div class="line-item">
                  <div class="zmb-img"></div>
                  <span class="ft-label">月度总目标：</span>
                  <span class="ft14">{{ goal.totalMonthlyGoal }}</span>
                </div>
              </div>
              <a-divider style="margin: 16px 0; background-color: rgba(56, 117, 255, 0.3)" />
              <!-- 子目标 -->
              <div v-for="sub in goal.monthlyGoalTaskDtoList" :key="sub.id" class="sub-target-box">
                <div class="sub-header" @click="toggleSubTarget(sub)">
                  <span
                    class="arrow-icon"
                    :class="{ rotated: expandedSet.has(sub.id) }"
                    v-if="
                                            (sub.storyList && sub.storyList.length > 0) ||
                                            (sub.taskList && sub.taskList.length > 0)
                                        "
                    ><RightOutlined style="font-size: 12px; color: #262626"
                  /></span>
                  <div v-else style="margin-right: 20px"></div>
                  <span class="sub-name">{{ sub.projectMonthlyGoal }}</span>
                </div>
                <div class="sub-desc" @click="toggleSubTarget(sub)">
                  <div style="margin-right: 20px"></div>
                  <template v-if="(sub.taskList && sub.taskList.length) || (sub.storyList && sub.storyList.length)">
                    <!--                    <div class="ft-label" >完成状态：</div>-->
                    <div class="tags-group-suolv">
                      <div class="tag-item" v-for="(story, index) in sub.taskList" :title="story.taskStatus" :style="{   backgroundColor: getStatusColor(story.taskStatus)   }">{{index}}</div>
                      <div class="tag-item-group" v-for="(story, index) in sub.storyList">
                        <div
                          class="tag-item"
                          :title="story.storyStatus"
                          :style="{
                          backgroundColor: getStatusColor(story.storyStatus)   }"
                        ></div>
                      </div>
                    </div>
                  </template>
                  <div class="ft-label">验收标准：</div>
                  <div class="ft14">{{ sub.acceptanceCriteria || "无" }}</div>
                </div>

                <div v-show="expandedSet.has(sub.id)" class="story-slot-wrapper" style="margin:0 24px">
                  <div class="story-item" v-for="(story, index) in sub.taskList" :key="story.id" v-if="goal.projectType === '交付' || goal.projectType === '市场'">
                    <div class="story-title">
                      <div class="title-left">
                        <div class="priority-tag" title="优先级" v-if="story.priority" :style="{   backgroundColor: getBgc(story.priority)   }">{{ story.priority }}</div>
                        <div
                          title="用户故事状态"
                          class="status-tag"
                          :style="{
                                                        backgroundColor: getStatusColor(story.taskStatus)
                                                    }"
                          >{{ story.taskStatus }}</div
                        >

                        <div class="story-name" :title="story.taskName">{{
                            story.taskName
                        }}</div>
                      </div>
                      <div class="title-right">
                        <a-space :size="8">
                          <div class="people-icon"></div>
                          <span class="title">创建人 :</span>
                          <span class="msg">{{ story.createBy }}</span>

                          <div class="time-icon"></div>
                          <span class="title">创建时间 :</span>
                          <span class="msg">{{ story.createTime }}</span>

                          <a-popconfirm title="确定取消关联吗?" ok-text="确定" cancel-text="取消" @confirm="cnacelTask(story.taskId, sub)" @cancel="cancel">
                            <a-button style="padding: 0" type="link" size="small">取消关联</a-button>
                          </a-popconfirm>
                        </a-space>
                        <!--                                                <a-space :size="4">-->
                        <!--                                                    <a-button-->
                        <!--                                                        size="small"-->
                        <!--                                                        type="link"-->
                        <!--                                                        @click="showQuestionMsg(story.description)"-->
                        <!--                                                        >查看描述</a-button-->
                        <!--                                                    >-->
                        <!--                                                    <a-divider-->
                        <!--                                                        type="vertical"-->
                        <!--                                                        style="margin: 0; background-color: #3875ff"-->
                        <!--                                                    />-->
                        <!--                                                    <a-button size="small" type="link" @click="handleEditStory(story)"-->
                        <!--                                                        >编辑</a-button-->
                        <!--                                                    >-->
                        <!--                                                    <a-divider-->
                        <!--                                                        type="vertical"-->
                        <!--                                                        style="margin: 0; background-color: #3875ff"-->
                        <!--                                                    />-->
                        <!--                                                    <a-popconfirm-->
                        <!--                                                        title="确定删除?"-->
                        <!--                                                        ok-text="确定"-->
                        <!--                                                        cancel-text="取消"-->
                        <!--                                                        @confirm="confirmDelete(story.id)"-->
                        <!--                                                        @cancel="cancel"-->
                        <!--                                                    >-->
                        <!--                                                        <a-button size="small" type="link">删除</a-button>-->
                        <!--                                                    </a-popconfirm>-->
                        <!--                                                </a-space>-->
                      </div>
                    </div>
                    <div class="content-body">
                      <div class="story-content">
                        <div class="item-icon"> </div>
                        <a-descriptions title="" bordered :column="4" size="small">
                          <a-descriptions-item label="项目阶段">
                            <div class="item-content" :title="story.milepostName">{{
                                story.milepostName
                            }}</div>
                          </a-descriptions-item>
                          <a-descriptions-item label="任务负责人">
                            <div class="item-content" :title="story.taskOwner">{{
                                story.taskOwner
                            }}</div>
                          </a-descriptions-item>
                          <a-descriptions-item label="任务执行人">
                            <div class="item-content" :title="story.taskParticipantStr">{{
                                story.taskParticipantStr
                            }}</div>
                          </a-descriptions-item>
                          <a-descriptions-item label="审核员">
                            <div class="item-content" :title="story.assessorName">{{
                                story.assessorName
                            }}</div>
                          </a-descriptions-item>
                          <a-descriptions-item label="计划开始">
                            <div class="item-content" :title="story.startTime">{{
                                story.startTime
                            }}</div>
                          </a-descriptions-item>

                          <a-descriptions-item label="计划结束">
                            <div class="item-content" :title="story.endTime">{{
                                story.endTime
                            }}</div>
                          </a-descriptions-item>
                          <a-descriptions-item label="实际开始">
                            <div class="item-content" :title="story.examPassTime">{{
                                story.examPassTime
                            }}</div>
                          </a-descriptions-item>
                          <a-descriptions-item label="实际结束">
                            <div class="item-content" :title="story.actualTaskFinishTime">{{
                                story.actualTaskFinishTime
                            }}</div>
                          </a-descriptions-item>
                        </a-descriptions>
                        <!-- 第一行 -->
                      </div>
                    </div>
                  </div>
                  <div class="story-item" v-for="(story, index) in sub.storyList" :key="story.id" v-if="goal.projectType === '产品研发'">
                    <div class="story-title">
                      <div class="title-left">
                        <div class="priority-tag" title="优先级" v-if="story.priority" :style="{   backgroundColor: getBgc(story.priority)   }">{{ story.priority }}</div>
                        <div
                          title="用户故事状态"
                          class="status-tag"
                          :style="{
                                backgroundColor: getStatusColor(story.storyStatus)
                             }"
                          >{{ story.storyStatus }}</div
                        >

                        <div class="story-name" :title="story.storyName">{{
                            story.storyName
                        }}</div>
                      </div>
                      <div class="title-right">
                        <a-space :size="8">
                          <div class="people-icon"></div>
                          <span class="title">创建人 :</span>
                          <span class="msg">{{ story.createdBy }}</span>

                          <div class="time-icon"></div>
                          <span class="title">创建时间 :</span>
                          <span class="msg">{{ story.createdTime }}</span>
                        </a-space>
                        <a-space :size="4">
                          <a-button size="small" type="link" @click="showQuestionMsg(story.description)">查看描述</a-button>
                          <!--                                                    <a-divider-->
                          <!--                                                        type="vertical"-->
                          <!--                                                        style="margin: 0; background-color: #3875ff"-->
                          <!--                                                    />-->
                          <!--                                                    <a-button size="small" type="link" @click="handleEditStory(story)"-->
                          <!--                                                        >编辑</a-button-->
                          <!--                                                    >-->
                          <!--                                                    <a-divider-->
                          <!--                                                        type="vertical"-->
                          <!--                                                        style="margin: 0; background-color: #3875ff"-->
                          <!--                                                    />-->
                          <a-popconfirm title="确定取消关联吗?" ok-text="确定" cancel-text="取消" @confirm="cnacelStory(story.id, sub)" @cancel="cancel">
                            <a-button type="link" style="padding: 0" size="small">取消关联1</a-button>
                          </a-popconfirm>
                        </a-space>
                      </div>
                    </div>
                    <div class="content-body">
                      <div class="story-content">
                        <div class="item-icon" v-if="story.labels">
                          <div v-for="(tag, index) in handlerGetSpace(story.labels)" class="label-item"> <div class="label-img"></div>{{ tag }} </div>
                        </div>
                        <a-descriptions title="" bordered :column="4" size="small">
                          <a-descriptions-item label="计划开始">
                            <div class="item-content" :title="story.startTime">{{
                                story.startTime
                            }}</div>
                          </a-descriptions-item>
                          <a-descriptions-item label="实际开始">
                            <div class="item-content" :title="story.actualStartTime">{{
                                story.actualStartTime
                            }}</div>
                          </a-descriptions-item>
                          <a-descriptions-item label="计划完成">
                            <div class="item-content" :title="story.endTime">{{
                                story.endTime
                            }}</div>
                          </a-descriptions-item>
                          <a-descriptions-item label="实际完成">
                            <div class="item-content" :title="story.actualEndTime">{{
                                story.actualEndTime
                            }}</div>
                          </a-descriptions-item>
                          <a-descriptions-item label="备注" :span="5">
                            <div class="item-content" :title="story.remark">{{
                                story.remark
                            }}</div>
                          </a-descriptions-item>
                        </a-descriptions>
                        <!-- 第一行 -->
                      </div>
                    </div>
                  </div>
                </div>
              </div>
              <a-divider style="margin: 16px 0; background-color: rgba(56, 117, 255, 0.3)" v-if="index == state.dataSource.length - 1" />
            </div>
          </a-spin>
        </div>
      </div>
      <div class="pagination-div">
        <a-pagination
          v-model:current="pagination.current"
          :total="pagination.total"
          :show-total="pagination.showTotal"
          :page-size="pagination.pageSize"
          :show-size-changer="true"
          @change="pageChange"
        />
      </div>
      <!-- end vid_p2x31ulxw6 自定义模板_gufjjaz2ct -->
      <!-- end vid_p2x31ulxw6 自定义模板_gufjjaz2ct -->
      <!-- begin vid_w7zzsiss6f 容器_q08c8hk2as -->
      <al-box v-if="false" class="vid_w7zzsiss6f">
        <!-- begin vid_isxswct1h6 新建 -->
        <a-button v-permission="'3000001093_vid_isxswct1h6'" class="vid_isxswct1h6"> 新建 </a-button>
        <!-- end vid_isxswct1h6 新建 -->
        <!-- begin vid_vljk3npb78 编辑 -->
        <a-button v-permission="'3000001093_vid_vljk3npb78'" class="vid_vljk3npb78"> 编辑 </a-button>
        <!-- end vid_vljk3npb78 编辑 -->
        <!-- begin vid_ork98p86ny 删除 -->
        <a-button v-permission="'3000001093_vid_ork98p86ny'" class="vid_ork98p86ny"> 删除 </a-button>
        <!-- end vid_ork98p86ny 删除 -->
        <!-- begin vid_008jlq241v 关联 -->
        <a-button v-permission="'3000001093_vid_008jlq241v'" class="vid_008jlq241v"> 关联 </a-button>
        <!-- end vid_008jlq241v 关联 -->
        <!-- begin vid_f474iqmj5j 项目配置 -->
        <a-button v-permission="'3000001093_vid_f474iqmj5j'" class="vid_f474iqmj5j"> 项目配置 </a-button>
        <!-- end vid_f474iqmj5j 项目配置 -->
        <!-- begin vid_0hmbaplbmh 甘特图 -->
        <a-button v-permission="'3000001093_vid_0hmbaplbmh'" class="vid_0hmbaplbmh"> 甘特图 </a-button>
        <!-- end vid_0hmbaplbmh 甘特图 -->
        <!-- begin vid_2zx50bmyi5 导出 -->
        <a-button v-permission="'3000001093_vid_2zx50bmyi5'" class="vid_2zx50bmyi5"> 导出 </a-button>
        <!-- end vid_2zx50bmyi5 导出 -->
        <!-- begin vid_e8d1qz4ux7 生成绩效 -->
        <a-button v-permission="'3000001093_vid_e8d1qz4ux7'" class="vid_e8d1qz4ux7"> 生成绩效 </a-button>
        <!-- end vid_e8d1qz4ux7 生成绩效 -->
        <!-- begin vid_bv6ql52jgn 批量修改完成系数 -->
        <a-button v-permission="'3000001093_vid_bv6ql52jgn'" class="vid_bv6ql52jgn"> 批量修改完成系数 </a-button>
        <!-- end vid_bv6ql52jgn 批量修改完成系数 -->
      </al-box>
      <!-- end vid_w7zzsiss6f 容器_q08c8hk2as -->
    </a-spin>
  </div>
</template>
<script setup lang="tsx">
  import {
      h, ref, reactive, toRaw, markRaw, watch, computed,
      onBeforeMount, onMounted, onBeforeUnmount, onUnmounted, onActivated, onDeactivated
    } from "vue";
    import { useRoute, useRouter } from 'vue-router';
    const router = useRouter();
    const route = useRoute();
    import { get, post, put, del, request, requestWithHeaders } from '@/utils/http/Axios';
    import { cloneDeep, localGet, merge, getDifferenceArray, traversalTreeStructure, checkCaseCondition, renderStringInTemplate, handleBreadcrumbJump, throttle, permission, getComponentParamsValue } from '@/utils/index';
    import { isNullOrEmpty, isEmptyArr, isNullOrUnDef, isContained, isArray, isEmpty, isObject } from '@/utils/is';
    import dayjs from 'dayjs';
    import { getPagePcChartsDataSourceConvert } from '@/utils/chart';
    import { message, notification, Modal } from 'ant-design-vue'
    import { propertyFormatByNumber, propertyFormatByPercentage, propertyFormatByDate, parseSubFromDataList } from '@/utils/format';
    import colorTheme from '@/design/custom-theme.json';
    
    import UserTableRecords from '@/model/UserTableRecords';
    import { getAppBaseUrl } from '@/utils/index';
    import { sendToken } from "@/hooks/useIframeToken";
    import { useSystemStore } from "@/store/modules/system";
    const systemStore = useSystemStore();
    



      // 获取传入的流程ID和组件参数
      const props = defineProps({
            'processInstanceId': {
            type: [String,Number,Boolean],
            default: undefined,
        },
      })
      const immediateWatch = (source, callback) => {
        watch(source, callback, {deep: true,immediate: true })
      }



  /* -------------------------- 属性定义 -------------------------- */

      const setTimeOutList = [];
      const pageLoading = reactive({
        loading: false,
        tip: undefined
      });
      const authInfo = localGet('app-user-store');




      // 处理校验
      const setSubFormName =(parentInfo, name)=>{
        return [parentInfo.parents, parentInfo.cycleIndex, name];
      }


  /* ========================== 属性定义 ========================== */


  /* -------------------------- 元素数据引用 -------------------------- */


  /* ========================== 元素数据引用 ========================== */


  /* -------------------------- 页面数据 -------------------------- */


  /* ========================== 页面数据 ========================== */



  /* -------------------------- 响应 -------------------------- */

  /* ========================== 响应 ========================== */


  /* -------------------------- 函数 -------------------------- */

  /* ========================== 函数 ========================== */


  /* -------------------------- 页面参数 -------------------------- */

    const pageParameter_state = reactive({
        'processInstanceId': props.processInstanceId ?? route.query.processInstanceId,
    })

  /* ========================== 页面参数 ========================== */


  /* -------------------------- 组件事件处理方法 -------------------------- */

    // ---------------------------- 组件数据同步 ----------------------------

    // ============================ 组件数据同步 ============================


  /* ========================== 组件事件处理方法 ========================== */


  /* -------------------------- 生命周期 -------------------------- */
  // 用于参数变更后重新执行自定义指令
      const queryUpdateFlag = ref(0);
      onMounted(() => { ;

    });

    onUnmounted(() => {
      // 销毁定时器
      setTimeOutList.forEach(({ repeat, timer }) => {
        repeat ?  clearInterval(timer): clearTimeout(timer);
      });
    });

  /* ========================== 生命周期 ========================== */


  /* -------------------------- 数据关联处理 -------------------------- */





  /* -------------------------- 表单数据同步 -------------------------- */
  /* ========================== 表单数据同步 ========================== */

  /* ========================== 数据关联处理 ========================== */


  /* -------------------------- 不同组件自定义的处理逻辑 -------------------------- */

  /* ========================== 不同组件自定义的处理逻辑 ========================== */


  // ================================定制化逻辑========================================
  const selectHolder = '请选择'
      const inputHolder = '请输入'
      onMounted(() => {
          const formattedMonth = dayjs().format('YYYY-MM')
          console.log(formattedMonth)
          state.searchForm.targetMonthList = [formattedMonth, formattedMonth]
          state.filter.month = formattedMonth
          getAllJfPeople()
          getData()
      })
      const peopleList = ref([])

      function getAllJfPeople() {
          get('/solution-ppm/api/v2/built-in-system-ppm/pmgf/get/allUser').then(({ data }) => {
              peopleList.value = data.userDtoList.map(item => {
                  return {
                      label: item.name,
                      value: item.id
                  }
              })
          })
      }

      const state = reactive({
          searchForm: {
              leaderList: [],
              projectNameList: [],
              projectTypeList: [],
              targetMonthList: []
          },
          loading: false,
          dataSource: [],
          projectList: [],
          allUser: [],
          completeVisible: false,
          okLoading: false,
          type: '完成系数',
          settingVisble: false,
          treeData: [],
          filter: {
              month: []
          }
      })
      const pageSizeChange = (current, size) => {
          pagination.value.current = current
          pagination.value.pageSize = size
          getData()
      }
      const pageChange = (page, pageSize) => {
          pagination.value.current = page
          pagination.value.pageSize = pageSize
          getData()
      }
      const pagination = ref({
          current: 1,
          pageSize: 10,
          total: 0,
          pageSizeOptions: ['20', '40', '60', '80', '100'],
          showTotal: total =>
              `共 ${total} 个项目 第 ${pagination.value.current}/${Math.ceil(total / pagination.value.pageSize)}页`
      })

      //     获取项目列表
      function getProjectList() {
          get('/solution-ppm/api/v2/built-in-system-ppm/pmgf/get/platformAndDeliveryProjects').then(data => {
              state.projectList = data.data.projectDtoList.map(item => {
                  return {
                      label: item.projectName,
                      value: item.projectName
                  }
              })
          })
      }

      //     获取项目列表
      function getProjectListAccordingType() {
          post('/solution-ppm/api/v2/built-in-system-ppm/pmgf/get/projectNames', {
              projectType: targetState.modalForm.projectType
          }).then(data => {
              targetState.projectList = data.data.projectDtoList.map(item => {
                  return {
                      label: item.projectName,
                      value: item.projectName
                  }
              })
          })
      }

      //     获取负责人
      function getAllUser() {
          get('/solution-ppm/api/v2/built-in-system-ppm/pmgf/get/allUser').then(data => {
              state.allUser = targetState.allUser = data.data.userDtoList.map(item => {
                  return {
                      label: item.name,
                      value: item.name
                  }
              })
          })
      }

      const form = ref(null)
      const activeKeys = ref([])

      function expendAll() {
          // 遍历每个顶层项目
          function recursiveExpand(data) {
              data.forEach(item => {
                  // 将当前项目的 projectId 添加到 activeKeys 中
                  activeKeys.value.push(item.projectId)

                  // 如果存在 children 并且是数组，则继续展开子节点
                  if (Array.isArray(item.children)) {
                      recursiveExpand(item.children)
                  }
              })
          }

          // 调用递归函数
          recursiveExpand(state.treeData)
      }

      // 递归树节点组件
      function showCompleteModal() {
          state.type = '完成系数'
          getComplete()
          state.completeVisible = true
      }

      function showSettingModal() {
          state.type = '是否展示'
          getSetting()
          state.completeVisible = true
      }

      // 生成绩效
      function handleGenerate() {
          targetState.generateLoading = true
          put('/solution-ppm/api/v2/built-in-system-ppm/emgf/v2/generate')
              .then(data => {
                  if (data.code !== 200) {
                      message.error(data.message)
                      return
                  }
                  message.success(data.message)
              })
              .finally(() => {
                  targetState.generateLoading = false
              })
      }

      // 导出
      function handleExport() {
          post('/solution-ppm/api/v2/built-in-system-ppm/pmgf/goals/export/permissionCheck', {}).then(data => {
              if (data.code !== 200) {
                  message.error(data.message)
                  return
              }
              post(
                  '/solution-ppm/api/v2/built-in-system-ppm/pmgf/goals/export ',
                  { targetMonthList: state.searchForm.targetMonthList },
                  { responseType: 'arraybuffer' }
              ).then(res => {
                  downloadExcel(res, '项目月度目标.xlsx')
              })
          })
      }

      async function getSetting() {
          try {
              treeLoading.value = true
              const response = await get('/solution-ppm/api/v2/built-in-system-ppm/pmgf/get_all_project_tree')
              if (response.code !== 200) {
                  message.error(response.message)
                  return null // 返回 null，表示获取数据失败
              }
              state.treeData = response.data
              expendAll() // 数据加载完成后展开所有节点
              return response.data // 返回数据
          } catch (error) {
              message.error(error)
              return null // 返回 null，表示发生错误
          } finally {
              treeLoading.value = false
          }
      }

      const treeLoading = ref(false)

      async function getComplete() {
          try {
              treeLoading.value = true
              const response = await get(
                  `/solution-ppm/api/v2/built-in-system-ppm/pmgf/get_no_goals_finish_coefficient/${state.filter.month}`
              )
              if (response.code !== 200) {
                  message.error(response.message)
                  return null // 返回 null，表示获取数据失败
              }
              state.treeData = response.data
              expendAll() // 数据加载完成后展开所有节点
              return response.data // 返回数据
          } catch (error) {
              message.error('数据获取失败')
              console.error(error)
              return null // 返回 null，表示发生错误
          } finally {
              treeLoading.value = false // 无论成功还是失败，最终都设置为 false，表示加载结束
          }
      }

      function submitComplete() {
          state.okLoading = true
          if (state.type === '完成系数') {
              put(
                  `/solution-ppm/api/v2/built-in-system-ppm/pmgf/modify_no_goals_finish_coefficient/${state.filter.month}`,
                  state.treeData
              )
                  .then(data => {
                      if (data.code !== 200) {
                          message.error(data.message)
                          return
                      }
                      message.success(data.message)
                      state.completeVisible = false
                  })
                  .finally(() => {
                      state.okLoading = false
                  })
          } else {
              put('/solution-ppm/api/v2/built-in-system-ppm/pmgf/modify_project_config', state.treeData)
                  .then(data => {
                      if (data.code !== 200) {
                          message.error(data.message)
                          return
                      }
                      message.success(data.message)
                      state.completeVisible = false
                  })
                  .finally(() => {
                      state.okLoading = false
                  })
          }
      }

      //导出
      const downloadExcel = (response, name) => {
          const blob = new Blob([response], {
              type: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet;charset=utf-8'
          })
          const downloadElement = document.createElement('a')
          const href = window.URL.createObjectURL(blob) // 创建下载的链接
          downloadElement.href = href
          downloadElement.download = name // 下载后文件名
          document.body.appendChild(downloadElement)
          downloadElement.click() // 点击下载
          document.body.removeChild(downloadElement) // 下载完成移除元素
          window.URL.revokeObjectURL(href)
          return href
      }
      import { nextTick } from 'vue'
      import Gante from './Page3000001091.vue'
      import { QuillEditor } from '@vueup/vue-quill'

      const targetState = reactive({
          dataSource: [],
          projectList: [],
          parentName: undefined,
          searchForm: {
              month: undefined
          },
          showCheck: false,
          targetLoadog: false,
          addOrEditVisible: false,
          addOrEditTitle: '',
          modalForm: {
              monthlyGoalObjectList: [],
              leaderList: [],
              associationProjectId: undefined,
              projectType: undefined,
              targetMonth: undefined,
              teamLeader: undefined,
              totalMonthlyGoal: undefined
          },
          allUser: [],
          expendAll: false,
          loading: false,
          ganteVisible: false,
          hiddenVisible: false,
          generateLoading: false
      })

      // 根据id查目录
      function getParentName() {
          get(`/solution-ppm/api/v2/built-in-system-ppm/pmgf/menu_name/${useProjectId.value}`).then(data => {
              targetState.parentName = data.data
          })
      }

      function getData() {
          targetState.loading = true
          return post('/solution-ppm/api/v2/built-in-system-ppm/pmgf/get/monthlyGoals', {
              ...state.searchForm,
              pageNum: pagination.value.current,
              pageSize: pagination.value.pageSize
          })
              .then(data => {
                  if (data.code !== 200) {
                      message.error(data.message)
                      return []
                  }
                  targetState.dataSource = data.data.monthlyGoalManagementDtoList
                  pagination.value.total = data.data.totalElements
                  return data.data.monthlyGoalManagementDtoList
              })
              .finally(() => {
                  targetState.loading = false
              })
      }

      function resetData() {
          state.searchForm.leaderList = []
          state.searchForm.projectNameList = []
          state.searchForm.projectTypeList = []
          getData()
      }

      const formRef = ref(null)
      const targetFormRef = ref(null)
      const targetItem = {
          monthlyGoal: undefined,
          acceptanceCriteria: undefined,
          goalWeight: ''
      }

      function handleAddTargetItem() {
          targetState.modalForm.monthlyGoalObjectList.push({ ...targetItem })
      }

      function handleDeleteTargetItem(index) {
          targetState.modalForm.monthlyGoalObjectList.splice(index, 1)
      }

      function handleAddTarget() {
          targetState.addOrEditVisible = true
          targetState.addOrEditTitle = '新建目标'
          getAllUser()
          // getParentName()
          targetState.modalForm.monthlyGoalObjectList.push({ ...targetItem })
      }

      const allExpanded = ref(false)

      // const toggleSubTarget = sub => {
      //     sub.expanded = !sub.expanded
      // }
      function toggleSubTarget(sub) {
          if (expandedSet.has(sub.id)) {
              expandedSet.delete(sub.id)
          } else {
              expandedSet.add(sub.id)
          }
      }

      //     展开收起
      const handleExpendAll = () => {
          allExpanded.value = !allExpanded.value

          targetState.dataSource.forEach(goal => {
              goal.monthlyGoalTaskDtoList.forEach(sub => {
                  if (allExpanded.value) {
                      expandedSet.add(sub.id)
                  } else {
                      expandedSet.delete(sub.id)
                  }
              })
          })
      }

      function handlerGetSpace(data) {
          return data?.split(/[,;；]/)
      }

      const colorMap = {
          '进行中': '#3875FF',
          '完成': '#52C41A',
          '未启动': '#8C8C8C',
          '未开始': '#8C8C8C',
          '已完成': '#52C41A',
          '延期': '#F5222D',
          '延期完成': '#FAAD14',
          '审批中': '#FAAD14',
          '下线': '#FAAD14',
          '已通过': '#52C41A'
      }

      function getStatusColor(status) {
          return colorMap[status] || '#8C8C8C'
      }


      const proityColor = {
        'P0': '#ff2a00',
        'P1': '#ffa940',
        'P2': '#ffa940',
        'P3': '#1890ff',
      }
      function getBgc(type) {
        type = type ? type.toUpperCase() : ''
        return proityColor[type]
      }

      //     用户故事
      const milepostState = reactive({
          searchForm: {
              storyStatus: undefined,
              storyName: undefined,
              directionField: 'created_time-desc',
              labels: undefined
          },
          current: 1,
          addOrEditVisible: false,
          addOrEditTitle: '',
          modalForm: {
              storyName: undefined,
              priority: undefined,
              labels: undefined,
              timeRangeList: [],
              taskList: [],
              templateTaskId: [],
              monthlyGoalTargetMonth: undefined,
              projectMonthlyGoalManagementId: undefined,
              remarks: undefined
          }
      })

      function cancelStory() {
          currentData.value = {}
          milepostState.addOrEditVisible = false
          milepostState.modalForm = {
              storyName: undefined,
              priority: undefined,
              labels: undefined,
              timeRangeList: [],
              taskList: [],
              templateTaskId: [],
              monthlyGoalTargetMonth: undefined,
              projectMonthlyGoalManagementId: undefined,
              remarks: undefined
          }
          milepostState.current = 1
      }

      const quillEditor = ref(null)
      const currentData = ref({})

      //     编辑story
      function handleEditStory(record) {
          console.log(record)
          const item = cloneDeep(record)
          Object.assign(milepostState.modalForm, item)
          milepostState.modalForm.timeRangeList = !item.startTime || !item.endTime ? [] : [item.startTime, item.endTime]
          currentData.value = item
          milepostState.addOrEditVisible = true
          milepostState.addOrEditTitle = '编辑用户故事'
          getTarget()
          nextTick(() => {
              let descriptionData = JSON.parse(record.description)
              quillEditor?.value?.setContents(descriptionData)
          })
      }

      function getTarget() {
          post('/solution-ppm/api/v2/built-in-system-ppm/pmgf/get/monthlyGoals', {
              targetMonthList: [
                  milepostState.modalForm.monthlyGoalTargetMonth,
                  milepostState.modalForm.monthlyGoalTargetMonth
              ]
          }).then(data => {
              if (data.code !== 200) {
                  message.error(data.message)
                  return
              }
              const allSubGoals = []

              data.data.monthlyGoalManagementDtoList?.forEach(item => {
                  item.monthlyGoalTaskDtoList?.forEach(sub => {
                      allSubGoals.push({
                          label: sub.projectMonthlyGoal,
                          value: sub.id
                      })
                  })
              })
              milepostState.targetList = allSubGoals
          })
      }

      const showMsgState = reactive({
          visible: false,
          msg: undefined,
          title: ''
      })

      function showQuestionMsg(msg) {
          if (!msg) {
              message.info('暂无描述')
              return
          }
          showMsgState.msg = msg
          showMsgState.visible = true
      }

      function cancelShowMsg() {
          showMsgState.msg = undefined
          showMsgState.visible = false
      }

      //   格式化文本展示
      function getHtmlContent(input) {
          // 防御性处理：避免 null 或 undefined
          if (!input) return ''

          // 尝试解析为富文本 Delta 格式
          let deltaObj = null
          try {
              const parsed = typeof input === 'string' ? JSON.parse(input) : input
              if (parsed?.ops && Array.isArray(parsed.ops)) {
                  deltaObj = parsed
              }
          } catch (e) {
              // 解析失败，说明不是 JSON 或不是 Delta 格式，走普通字符串逻辑
          }

          // 如果是富文本格式
          if (deltaObj) {
              try {
                  const tempEl = document.createElement('div')
                  const quill = new Quill(tempEl)
                  quill.setContents(deltaObj)
                  return quill.root.innerHTML
              } catch (err) {
                  console.error('富文本渲染失败', err)
                  return '' // 保险起见返回空
              }
          }

          // 否则是普通文本，做一下换行处理
          return String(input).replace(/\n/g, '<br/>')
      }

      //     富文本设置
      import { nextTick } from 'vue'
      import { QuillEditor, Quill } from '@vueup/vue-quill'
      import ImageUploader from 'quill-image-uploader'
      import '@vueup/vue-quill/dist/vue-quill.snow.css'
      import { take } from 'lodash-es'

      const titleConfig = [
          { Choice: ' .ql-bold', title: '加粗' },
          { Choice: ' .ql-italic', title: '斜体' },
          { Choice: ' .ql-underline', title: '下划线' },
          { Choice: ' .ql-strike', title: '删除线' },
          { Choice: ' .ql-blockquote', title: '块引用' },
          { Choice: ' .ql-code-block', title: '插入代码' },
          { Choice: ' .ql-size', title: '字体大小' },
          { Choice: ' .ql-size', title: '字体大小' },
          { Choice: ' .ql-color', title: '字体颜色' },
          { Choice: ' .ql-background', title: '字体背景颜色' },
          { Choice: ' .ql-list[value="ordered"]', title: '有序列表' },
          { Choice: ' .ql-list[value="bullet"]', title: '无序列表' },
          { Choice: ' .ql-header[value="1"]', title: '1级标题' },
          { Choice: ' .ql-header[value="2"]', title: '2级标题' },
          { Choice: ' .ql-align', title: '对齐方式' },
          { Choice: ' .ql-clean', title: '清除字体格式' },
          { Choice: ' .ql-image', title: '图像' },
          { Choice: ' .ql-size .ql-picker-item[data-value="small"]', title: '小号' },
          { Choice: ' .ql-size .ql-picker-item[data-value="large"]', title: '大号' },
          { Choice: ' .ql-size .ql-picker-item[data-value="huge"]', title: '超大号' },
          { Choice: ' .ql-size .ql-picker-item:nth-child(2)', title: '标准' },
          { Choice: ' .ql-align .ql-picker-item:first-child', title: '居左对齐' },
          { Choice: ' .ql-align .ql-picker-item[data-value="center"]', title: '居中对齐' },
          { Choice: ' .ql-align .ql-picker-item[data-value="right"]', title: '居右对齐' },
          { Choice: ' .ql-align .ql-picker-item[data-value="justify"]', title: '两端对齐' }
      ]
      // 注册图片上传模块
      Quill.register('modules/imageUploader', ImageUploader)

      // 将本地文件转换为URL
      const getLocalImageURL = file => {
          return new Promise(resolve => {
              const reader = new FileReader()
              reader.onload = e => {
                  resolve(e.target.result)
              }
              reader.readAsDataURL(file)
          })
      }

      // 表单数据

      // Quill 编辑器选项
      const editorOption = ref({
          modules: {
              // imageUploader: {
              //     upload: async file => {
              //         const localUrl = await getLocalImageURL(file)
              //         return localUrl // 返回本地图片的 URL 进行预览
              //     }
              // },
              toolbar: [
                  ['bold', 'italic', 'underline', 'strike'], // 加粗，斜体，下划线，删除线
                  ['blockquote', 'code-block'], // 引用，代码块
                  [{ header: 1 }, { header: 2 }], // 标题1，标题2
                  [{ list: 'ordered' }, { list: 'bullet' }], // 有序列表，无序列表
                  [{ size: ['small', false, 'large', 'huge'] }], // 文字大小
                  [{ color: [] }, { background: [] }], // 字体颜色，背景颜色
                  [{ align: [] }], // 对齐
                  ['clean'], // 清除格式
                  ['image'] // 链接，图片，视频
              ]
              // ImageUploader: imageHandler
          }
      })
      // 上传API
      const uploadFileAPI = async file => {
          const data = new FormData()
          data.append('file', file)

          return post('/file-storage/api/v1/file/upload', data)
              .then(({ data: { fullUrl } }) => {
                  return { data: { fullUrl } }
              })
              .catch(error => {
                  console.error('上传图片出错:', error)
                  throw error // 抛出错误以供外部处理
              })
      }

      // 将 dataURL 转换为 File 对象的辅助函数
      const dataURLtoFile = (dataurl, filename) => {
          const arr = dataurl.split(',')
          const mime = arr[0].match(/:(.*?);/)[1]
          const bstr = atob(arr[1])
          let n = bstr.length
          const u8arr = new Uint8Array(n)
          while (n--) {
              u8arr[n] = bstr.charCodeAt(n)
          }
          return new File([u8arr], filename, { type: mime })
      }

      function initTitle() {
          document.getElementsByClassName('ql-editor')[0].dataset.placeholder = ''
          for (let item of titleConfig) {
              let tip = document.querySelector('.ql-toolbar' + item.Choice)
              if (!tip) continue
              tip.setAttribute('title', item.title)
          }
      }

      function confirmDelete(id) {
          del(`/solution-ppm/api/v2/built-in-system-ppm/project/story/${id}`).then(data => {
              if (data.code !== 200) {
                  message.error(data.message)
                  return
              }
              message.success(data.message)
              getData()
          })
      }

      //     用户故事
      //     展示gante
      const gantMonth = ref()
      const gantProjectName = ref()

      function showGante(record) {
          gantMonth.value = record.targetMonth
          gantProjectName.value = record.projectName
          targetState.ganteVisible = true
      }

      function cancelGante() {
          targetState.ganteVisible = false
      }

      //     删除
      const currentHiddenData = ref({})

      function showHidden(record) {
          currentHiddenData.value = record
          targetState.hiddenVisible = true
      }

      // 编辑
      const currentEditData = ref({})

      function handleEditGoal(record) {
          getAllUser()
          get(`/solution-ppm/api/v2/built-in-system-ppm/pmgf/get/monthlyGoals/${record.id}`).then(data => {
              currentEditData.value = data.data
              console.log(data.data)
              Object.assign(targetState.modalForm, data.data)
              getProjectListAccordingType()
              targetState.addOrEditVisible = true
              targetState.addOrEditTitle = '编辑目标'
          })
      }

      function submitTarget() {
          targetFormRef.value.validate().then(() => {
              const url = currentEditData.value.overallProjectId
                  ? '/solution-ppm/api/v2/built-in-system-ppm/pmgf/edit/monthlyGoal'
                  : '/solution-ppm/api/v2/built-in-system-ppm/pmgf/add/monthlyGoal'
              targetState.targetLoadog = true
              post(url, {
                  ...targetState.modalForm,
                  overallProjectId: currentEditData.value.overallProjectId ? currentEditData.value.overallProjectId : null
              })
                  .then(data => {
                      if (data.code !== 200) {
                          message.error(data.message)
                          return
                      }
                      message.success(data.message)
                      cancelTarget()
                      getData()
                  })
                  .finally(() => {
                      targetState.targetLoadog = false
                  })
          })
      }

      function cancelTarget() {
          targetState.addOrEditVisible = false
          targetState.modalForm = {
              monthlyGoalObjectList: [],
              leaderList: [],
              associationProjectId: undefined,
              projectType: undefined,
              targetMonth: undefined,
              teamLeader: undefined,
              totalMonthlyGoal: undefined
          }
      }

      function confirmDeleteGoal(goal) {
          del(`/solution-ppm/api/v2/built-in-system-ppm/pmgf/delete/monthlyGoals/${goal.overallProjectId}`).then(data => {
              if (data.code !== 200) {
                  message.error(data.message)
                  return
              }
              message.success(data.message)
              getData()
          })
      }

      //     关联
      function handleAssociation(goal) {
          window.open(
              `${import.meta.env.VITE_PUBLIC_PATH}/page/3000001102?projectName=${goal.projectName}&projectType=${
                  goal.projectType
              }&id=${goal.overallProjectId}`,
              '_blank'
          )
      }
      const expandedSet = reactive(new Set()) // 用来存放展开的 sub.id
      //     取消关联
      function cnacelStory(id, sub) {
          del(`/solution-ppm/api/v2/built-in-system-ppm/pmgf/cancel/relatedStory/${id}`).then(data => {
              if (data.code !== 200) {
                  message.error(data.message)
                  return
              }
              message.success(data.message)
              // 保留需要展开的 ID
              expandedSet.add(sub.id)

              // 重新获取数据
              getData()
          })
      }

      function cnacelTask(id, sub) {
          del(`/solution-ppm/api/v2/built-in-system-ppm/pmgf/cancel/relatedTask/${id}`).then(data => {
              if (data.code !== 200) {
                  message.error(data.message)
                  return
              }
              message.success(data.message)
              expandedSet.add(sub.id)

              // 重新获取数据
              getData()
          })
      }
</script>
<style lang="less" scoped>
  .page_root {
  width: 100%;
  height: 100%;
  overflow: auto;
  }
  .page_root :deep(.@{ant-prefix}-spin-nested-loading),
  .page_root :deep(.@{ant-prefix}-spin-container)
   {
      height: 100%;
  }
  .page_root :deep(.@{ant-prefix}-spin-container .@{ant-prefix}-table-wrapper)
   {
      display: flex;
      flex-flow: column nowrap;
      justify-content: flex-start;
  }
  .page_root :deep(.@{ant-prefix}-table)
   {
    flex: auto;
    overflow: auto;
  }
  .table-moreBtn_down {
    overflow: hidden; white-space: nowrap; text-overflow: ellipsis; width: 100px;
  }

  .table-moreBtn_menu :deep(.table-moreBtn_menu-item):hover {
    background: #ebf1ff;
  }

  /*  表格树结构样式处理，展开按钮层级增加*/
  :deep(.@{ant-prefix}-table-row-expand-icon) {
    z-index: 1;
  }
  /*  表格树结构 由于每个表格项采用自定义组件，使用绝对定位布局，开启树结构导致显示异常，暂时使用层级定位位置 */
  :deep(.@{ant-prefix}-table-row-level-1 .@{ant-prefix}-table-cell-with-append .cell-wrapper-left) {
    left: 15px !important;
    width: calc(100% - 15px);
  }
  :deep(.@{ant-prefix}-table-row-level-2 .@{ant-prefix}-table-cell-with-append .cell-wrapper-left) {
    left: 30px !important;
    width: calc(100% - 30px);
  }
  :deep(.@{ant-prefix}-table-row-level-3 .@{ant-prefix}-table-cell-with-append .cell-wrapper-left) {
    left: 45px !important;
    width: calc(100% - 45px);
  }
  :deep(.@{ant-prefix}-table-row-level-4 .@{ant-prefix}-table-cell-with-append .cell-wrapper-left) {
    left: 60px !important;
    width: calc(100% - 60px);
  }

  /* 穿梭框改变默认样式，为根据组件样式控制左右栏宽度。 */
  :deep(.@{ant-prefix}-transfer-list)
   {
      height: 100%;
      width: 50%;
  }
  .vid_w7zzsiss6f{
      padding-top:24px;
      padding-bottom:24px;
      background-color:#FF0707
  }
  .vid_isxswct1h6{
      box-shadow:0px 0px 0px 0px
  }
  .vid_ork98p86ny{
      box-shadow:0px 0px 0px 0px
  }
  .vid_0hmbaplbmh{
      box-shadow:0px 0px 0px 0px
  }
  .vid_bv6ql52jgn{
      box-shadow:0px 0px 0px 0px
  }

  /*样式*/
  .body {
    overflow: hidden;
    position: relative;
    height: 100%;
  }
  .top-search {
    height: 64px;
    margin-bottom: 14px;
    padding: 16px 24px;
    padding-bottom: 10px;
    border-radius: 0px;
    background-color: #fff;
  }

  .top-title {
    display: flex;
    align-items: center;
    padding: 16px 24px;
    justify-content: space-between;
    background-color: #fff;
  }
  .title-msg {
    padding-left: 8px;
    font-weight: 800;
    font-size: 16px;
    line-height: 16px;
    box-shadow: 0 0;
    border-left-style: solid;
    border-left-width: 4px;
    border-left-color: #3875ff;
  }
  .no-data-image {
    width: 66px;
    height: 80px;
    background-image: url('@/assets/images/f4999963200e6893629a63a4a771ba2a.png');
    background-size: cover;
    position: absolute;
    top: 50%;
    left: 50%;
    transform: translate(-50%, -50%);
  }
  .no-date-tip {
    font-size: 14px;
    color: #595959;
    letter-spacing: 0;
    font-weight: 400;
    margin-top: 84px;
  }
  .pagination-div {
    width: 100%;
    position: absolute;
    bottom: 0;
    padding: 10px;
    display: flex;
    justify-content: end;
    border-top: 1px solid #d9d9d9;
    background: #fff; /* 可选：为背景添加颜色 */
  }

  .modal-top-complete {
    margin-bottom: 16px;
  }
  .modal-top-setting {
    height: 40px;
    background: rgba(56, 117, 255, 0.1);
    border-radius: 0px;
    padding: 10px 16px;
    line-height: 20px;
    font-size: 14px;
    color: #262626;
    letter-spacing: 0;
    line-height: 20px;
    font-weight: 400;
    margin-bottom: 16px;
  }
  /*样式*/
  .modal-form :deep(.ant3-form-item-label) {
    width: 100px;
  }
  .reset-btn {
    color: #262626;
    background-color: #eeeeee;
    border-color: #eeeeee;
    border-radius: 0px;
  }
  .reset-btn:hover {
    background: #3875ff;
    border-color: #d9d9d9;
    color: #fff;
  }
  /*目标部分样式*/

  .goal-title-bar {
    height: 40px;
    display: flex;
    justify-content: space-between;
    align-items: center;
    margin-bottom: 14px;
    padding-top: 10px;
    //background-image: linear-gradient(270deg, rgba(56, 117, 255, 0) 0%, rgba(56, 117, 255, 0.15) 100%);
    //box-shadow: inset 4px 0 0 0 #3875ff;
    //border-left: 1px solid #3875ff;
    .ft16 {
      font-size: 14px;
      color: #262626;
      letter-spacing: 0;
      font-weight: 500;
    }
    .ft14 {
      font-size: 14px;
      color: #262626;
      letter-spacing: 0;
      font-weight: 500;
    }
    .ft-label {
      font-size: 14px;
      color: #595959;
      letter-spacing: 0;
      font-weight: 400;
    }
  }

  .goal-info {
    display: flex;
    gap: 8px;
    align-items: center;
    flex: 1;
    min-width: 0;
  }

  .goal-month {
    color: #1890ff;
    font-weight: 600;
  }

  .goal-product-jf,
  .goal-product-cp,
  .goal-product-sc {
    border-radius: 0px;
    width: 72px;
    height: 22px;
    text-align: center;
    font-size: 14px;
    letter-spacing: 0;
    line-height: 22px;
    font-weight: 500;
  }
  .goal-product-cp,
  .goal-product-sc {
    background: #722ed1;
    color: #fff;
  }
  .goal-product-jf {
    width: 44px;
    background:  #f759ab;
    color: #fff;
  }

  .goal-name {
    color: #000;
    white-space: nowrap;
    overflow: hidden;
    text-overflow: ellipsis;
    flex: 1;
    min-width: 0;
  }
  .goal-ops {
    display: flex;
    gap: 8px;
    align-items: center;
  }
  .approve-img,
  .time-img,
  .xs-img,
  .trd-img,
  .tl-img,
  .fzr-img,
  .zmb-img {
    width: 16px;
    height: 16px;
    background-size: cover;
  }
  .approve-img {
    background-image: url('@/assets/images/f96584b402ad5b7837477aba6c61cde0.png');
  }
  .time-img {
    margin-left: 8px;
    background-image: url('@/assets/images/39d3679c035fcca597f241d2a993ca2d.png');
  }
  .xs-img {
    background-image: url('@/assets/images/1134080a31d6436ad6877de2ae2c217d.png');
  }
  .trd-img {
    background-image: url('@/assets/images/977243802aea50848e4f6e4bc7087703.png');
  }
  .tl-img {
    background-image: url('@/assets/images/e8de86e64783438b993e99dbd7860987.png');
  }
  .fzr-img {
    background-image: url('@/assets/images/5f4b23b143e802968fa33921c37404cc.png');
  }
  .zmb-img {
    background-image: url('@/assets/images/25fb6d04d6ca3228d9c177c26d0a9e34.png');
  }
  .btn-no-margin {
    padding: 0;
  }
  .first-line,
  .second-line {
    display: flex;
    gap: 24px;
    align-items: center;
    margin-bottom: 8px;
    .ft14 {
      font-size: 14px;
      color: #262626;
      letter-spacing: 0;
      font-weight: 400;
    }
    .ft-label {
      font-size: 14px;
      color: #595959;
      letter-spacing: 0;
      font-weight: 400;
    }
  }
  .line-item {
    display: flex;
    gap: 8px;
    align-items: center;
  }

  .sub-target-box {
    margin-bottom: 20px;
  }
  .sub-target-box:last-child {
    margin-bottom: 0;
  }

  .sub-header {
    display: flex;
    align-items: center;
    justify-content: start;
    cursor: pointer;
    //white-space: pre-wrap;
  }

  .arrow-icon {
    font-size: 12px;
    transition: transform 0.2s;
    margin-right: 8px;
    color: #888;
  }

  .arrow-icon.rotated {
    transform: rotate(90deg);
  }

  .sub-name {
    font-size: 14px;
    color: #262626;
    letter-spacing: 0;
    font-weight: 600;
  }

  .sub-desc {
    font-size: 12px;
    color: #979797;
    letter-spacing: 0;
    font-weight: 600;
    display: flex !important;
    padding-bottom: 10px;
    cursor: pointer;
    display: flex;
    align-items: center;
    padding-top: 8px;
    .ft14 {
      font-size: 12px;
      color: #979797;
      letter-spacing: 0;
      font-weight: 500;
      flex: 1;
    }
    .ft-label {
      font-size: 12px;
      color: #979797;
      letter-spacing: 0;
      font-weight: 400;
    }
  }

  .expand-link {
    color: #1890ff;
    font-size: 14px;
    margin-left: 8px;
    white-space: nowrap;
  }

  .story-slot-wrapper {
    background: #fff;
    margin-bottom: 0 24px;
  }
  .story-item {
    box-shadow: 0 2px 5px 0 #c9dfff;
    border-radius: 0px;
    margin-bottom: 20px;
    .btn-opration {
      background-color: #ebf1ff;
      color: #3875ff;
    }
    :deep(.ant3-descriptions-view) {
      table {
        table-layout: fixed !important; /* 固定表格布局 */
        width: 100% !important;
        color: red;
      }
    }
    :deep(.ant3-descriptions-view) {
      table {
        table-layout: fixed !important; /* 固定表格布局 */
        width: 100% !important;
        color: red;
      }
    }
    :deep(.ant3-descriptions-bordered.ant3-descriptions-small .ant3-descriptions-item-label) {
      padding: 8px 8px;
    }
    :deep(.ant3-descriptions-bordered.ant3-descriptions-small .ant3-descriptions-item-content) {
      padding: 8px 8px;
    }
    .time-icon,
    .people-icon,
    .jz-icon {
      width: 16px;
      height: 16px;
      background-size: cover;
    }
    .time-icon {
      background-image: url('@/assets/images/39d3679c035fcca597f241d2a993ca2d.png');
    }
    .people-icon {
      background-image: url('@/assets/images/11cd4c52425c55e07df4079d77072f8c.png');
    }
    .story-name {
      white-space: nowrap;
      overflow: hidden;
      text-overflow: ellipsis;
      flex: 1;
      min-width: 0; /* 必须设置 */
    }

    .story-title {
      width: 100%;
      display: flex;
      justify-content: space-between;
      background-image: linear-gradient(270deg, rgba(105, 173, 255, 0.05) 0%, rgba(56, 117, 255, 0.1) 100%);
      border-radius:  0;
      padding: 9px 24px;
      gap: 16px;
      align-items: center;
      left: 0;
    }
    .title-left {
      display: flex;
      gap: 8px;
      font-size: 16px;
      color: #262626;
      letter-spacing: 0;
      font-weight: 600;
      align-items: center;
      flex: 1;
      min-width: 0; /* 防止子元素撑破父容器 */
    }
    .title-right {
      display: flex;
      align-items: center;
    }
    .status-tag,
    .priority-tag {
      font-size: 14px;
      color: #ffffff;
      letter-spacing: 0;
      text-align: center;
      line-height: 22px;
      padding: 0 4px;
      font-weight: 500;
      min-width: 32px;
      height: 22px;
      border-radius: 0;
      text-align: center;
    }
    .priority-tag {
      background: #40a9ff;
      border-radius: 0px;
      font-style: oblique;
    }
    .content-body {
    }
    .story-content {
      padding:10px;
    }
    .item-title {
      white-space: nowrap;
      font-family: PingFangSC-Regular;
      font-size: 14px;
      color: #595959;
      letter-spacing: 0;
      text-align: right;
      font-weight: 400;
    }

    .item-content {
      white-space: nowrap;
      overflow: hidden;
      text-overflow: ellipsis;
      cursor: default;
      font-family: PingFangSC-Medium;
      font-size: 14px;
      color: #262626;
      letter-spacing: 0;
      font-weight: 600;
    }
    .item-icon {
      display: flex;
      flex-wrap: wrap;
      gap: 8px; /* 可选：让 tag 之间有间距 */
      margin: 16px 0;
    }
    .label-item {
      display: flex;
      background-color: #eeeeee;
      align-items: center;
      padding: 1px 8px;
      font-size: 14px;
      color: #595959;
      letter-spacing: 0;
      text-align: center;
      font-weight: 400;
      gap: 4px;
      border-radius: 0px;
    }
    .label-img {
      background-image: url('@/assets/images/41210ac3a80806ed1005d4eea85d458a.png');
      background-size: cover;
      width: 10px;
      height: 10px;
    }
    .target-item {
      align-items: center;
    }
  }
  .form-model :deep(.ant3-form-item-label) {
    width: 110px;
  }

  .content {
    padding: 24px;
    background-color: #fff;
    border-radius: 0px;
    height: calc(100% - 194px);
    overflow: auto;

    /* 额外加个内层容器做 padding 避免问题 */
    display: flex;
    flex-direction: column;
  }
  .goal-card {
    flex: 1;
    display: flex;
    flex-direction: column;
    justify-content: space-between;
    background-image: linear-gradient(to bottom, #f2f6fc, #fff 80px);
    padding-left: 24px;
    padding-bottom:16px;
    margin-bottom: 16px;
    box-shadow: 0 2px 8px  #f2f6fc;
  }
  /*目标部分样式*/

  .tags-group-suolv{
    display: flex;
    align-items: center;
    justify-content: flex-start;
    margin-right: 14px;
    padding-right: 14px;
    border-right: 1px solid #dcdfe6;
    height: 12px;
    gap:1px;
    .tag-item-group{
      display: flex;
    }
    .tag-item{
      min-width: 10px;
      width: 10px;
      height: 8px;
      font-size:0;
      &.tag-item-b{
        width: 2px;
      }
    }

  }
</style>